home *** CD-ROM | disk | FTP | other *** search
- unit HVExceptNotify;
- // Unit that provides a notification service when exceptions are being raised
- //
- // Written by Hallvard Vassbotn, hallvard@balder.no, September 1999
- interface
-
- type
- TExceptNotify = procedure (ExceptObj: TObject; ExceptAddr: pointer; OSException: boolean);
- var
- ExceptNotify: TExceptNotify;
-
- implementation
-
- uses
- Windows,
- SysUtils,
- HVHookDLL;
-
- var
- Kernel32_RaiseException : procedure (dwExceptionCode, dwExceptionFlags, nNumberOfArguments: DWORD;
- lpArguments: PDWORD); stdcall;
-
- type
- PExceptionArguments = ^TExceptionArguments;
- TExceptionArguments = record
- ExceptAddr: pointer;
- ExceptObj : TObject;
- end;
-
- procedure HookedRaiseException(ExceptionCode, ExceptionFlags, NumberOfArguments: DWORD;
- Arguments: PExceptionArguments); stdcall;
- // All calls to Kernel32.RaiseException ends up here
- const
- // D2 has a different signature for Delphi exceptions
- cDelphiException = {$IFDEF VER90}$0EEDFACE{$ELSE}$0EEDFADE{$ENDIF};
- cNonContinuable = 1;
- begin
- // We're only interested in Delphi exceptions raised from System's
- // internal _RaiseExcept routine
- if (ExceptionFlags = cNonContinuable) and
- (ExceptionCode = cDelphiException) and
- (NumberOfArguments = 7) and
- (DWORD(Arguments) = DWORD(@Arguments) + 4) then
- begin
- // Run the event if it has been assigned
- if Assigned(ExceptNotify) then
- ExceptNotify(Arguments.ExceptObj, Arguments.ExceptAddr, false);
- end;
- // Call the original routine in Kernel32.DLL
- Kernel32_RaiseException(ExceptionCode, ExceptionFlags, NumberOfArguments, PDWORD(Arguments));
- end;
-
- var
- SysUtils_ExceptObjProc: function (P: PExceptionRecord): Exception;
-
- function HookedExceptObjProc(P: PExceptionRecord): Exception;
- begin
- // Non-Delphi exceptions such as AVs, OS and hardware exceptions
- // end up here. This routine is normally resposible for creating
- // a Delphi Exception object corresponding to the OS-level exception
- // described in the TExceptionRecord structure.
- //
- // We leave the mapping to the standard SysUtils routine,
- // but hook this to know about the exception and call our
- // event.
-
- // First call the original mapping function in SysUtils
- Result := SysUtils_ExceptObjProc(P);
-
- // Run the event if it has been assigned
- if Assigned(ExceptNotify) then
- ExceptNotify(Result, P^.ExceptionAddress, true);
- end;
-
- initialization
- SysUtils_ExceptObjProc := System.ExceptObjProc;
- System.ExceptObjProc := @HookedExceptObjProc;
- HookImport('Kernel32.dll', 'RaiseException', @HookedRaiseException, @Kernel32_RaiseException)
-
- finalization
- UnHookImport('Kernel32.dll', 'RaiseException', @HookedRaiseException, @Kernel32_RaiseException);
- System.ExceptObjProc := @SysUtils_ExceptObjProc;
- SysUtils_ExceptObjProc := nil;
-
- end.
-
-
-